package com.agileai.esb.smc.controller.ws8mf;

import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;

import org.apache.http.Consts;
import org.apache.http.HttpEntity;
import org.apache.http.NameValuePair;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.entity.UrlEncodedFormEntity;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.message.BasicNameValuePair;

import com.agileai.domain.DataParam;
import com.agileai.domain.DataRow;
import com.agileai.esb.component.manager.MessageFlowManager;
import com.agileai.esb.model.FlowConfigDocument.FlowConfig;
import com.agileai.esb.model.HttpRequestEndPointType;
import com.agileai.esb.model.InboundType;
import com.agileai.esb.smc.bizmoduler.ws8mf.MfProfileManage;
import com.agileai.hotweb.annotation.PageAction;
import com.agileai.hotweb.controller.core.BaseHandler;
import com.agileai.hotweb.renders.AjaxRenderer;
import com.agileai.hotweb.renders.LocalRenderer;
import com.agileai.hotweb.renders.ViewRenderer;
import com.agileai.util.IOUtil;

public class HttpFlowInvokeHandler extends BaseHandler{
	
	public ViewRenderer prepareDisplay(DataParam param) {
		String mfId = param.get("mfId");
		String appId = param.get("appId");
		this.setAttribute("mfId", mfId);
		this.setAttribute("appId", appId);
		DataParam dataParam = new DataParam("MF_ID",mfId,"APP_ID",appId);
		MfProfileManage mfProfileManage = this.lookupService(MfProfileManage.class);
		DataRow row = mfProfileManage.getRecord(dataParam);
		this.setAttributes(row);
		String appName = row.stringValue("APP_NAME");
		try {
			MessageFlowManager messageFlowManager = MessageFlowManager.instance(appName);
			FlowConfig flowConfig = messageFlowManager.getFlowConfig(mfId);
			InboundType inboundType = flowConfig.getInbound();
			HttpRequestEndPointType httpRequestEndPointType = inboundType.getHttpRequestEndPoint();
			String[] paramArray = httpRequestEndPointType.getParameterArray();
			List<DataRow> records = new ArrayList<DataRow>();
			if (paramArray != null && paramArray.length > 0){
				for (int i=0;i < paramArray.length;i++){
					DataRow tempRow = new DataRow();
					String key = paramArray[i];
					tempRow.put("PARAM_CODE",key);
					records.add(tempRow);
				}
			}
			this.setRsList(records);
		} catch (Exception e) {
			this.log.error(e.getLocalizedMessage(),e);
		}
		return new LocalRenderer(getPage());
	}
	
	@PageAction
	public ViewRenderer invokeMsgFlow(DataParam param){
		String rspText = FAIL;
		try {
			String requestURL = param.get("_mfAddress");
			CloseableHttpClient httpclient = HttpClients.createDefault();
			RequestConfig requestConfig = RequestConfig.custom()
					.setSocketTimeout(10000)
		            .setConnectTimeout(10000)
		            .setConnectionRequestTimeout(10000)
//		            .setProxy(new HttpHost("myotherproxy", 8080))
		            .build();
			HttpPost httpPost = new HttpPost(requestURL);
	    	httpPost.setConfig(requestConfig);
	        HttpEntity reqHttpEntity = buildHttpEntity(param);
	        httpPost.setEntity(reqHttpEntity);
	        CloseableHttpResponse httpResponse = httpclient.execute(httpPost);
	        HttpEntity httpEntity = httpResponse.getEntity();
			InputStream inputStream = httpEntity.getContent();
			ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
			IOUtil.copyAndCloseInput(inputStream, byteArrayOutputStream);
			String responseBody = byteArrayOutputStream.toString("UTF-8");
	        rspText = responseBody;
		} catch (Exception e) {
			log.error(e.getLocalizedMessage(),e);
			rspText = e.getLocalizedMessage();
		}
		return new AjaxRenderer(rspText);
	}	
	
	private HttpEntity buildHttpEntity(DataParam param){
		Iterator<String> iter = param.keySet().iterator();
		List<NameValuePair> formparams = new ArrayList<NameValuePair>();
		while(iter.hasNext()){
			String fieldName = iter.next();
			if ("_mfName".equals(fieldName) || "_mfAlias".equals(fieldName) || "_mfAddress".equals(fieldName)
					|| "_mfResponse".equals(fieldName)|| "actionType".equals(fieldName)|| "_mfResponse".equals(fieldName) || "invokeButton".equals(fieldName)){
				continue;
			}
			String value = param.get(fieldName);
			formparams.add(new BasicNameValuePair(fieldName, value));
		}
		HttpEntity result = new UrlEncodedFormEntity(formparams, Consts.UTF_8);
		return result;
	}
}
